﻿using Microsoft.AspNetCore.Authentication.JwtBearer;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.DependencyInjection.Extensions;
using Microsoft.IdentityModel.Tokens;
using System;
using System.Text;

namespace Canteen.Core.Common
{
    public static class JwtAuthSetup
    {
        public static void AddJwtAuthSetup(this IServiceCollection services, IConfiguration configuration)
        {
            if (services == null) throw new ArgumentNullException(nameof(services));
            var configure = configuration.GetSection(JwtAuthOptions.Configure);
            var options = configure.Get<JwtAuthOptions>();
            services.Configure<JwtAuthOptions>(configure);
            services.TryAddScoped<IJwtAuth, JwtAuth>();

            //Jwt验证服务依赖
            services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
                .AddJwtBearer(setupAction =>
                {
                    setupAction.TokenValidationParameters = new TokenValidationParameters()
                    {
                        ValidateIssuer = true,//验证谁发布的token(颁发者)
                        ValidIssuer = options.Issuer,

                        ValidateAudience = true,//验证token发布给谁(受理者)
                        ValidAudience = options.Audience,

                        ValidateIssuerSigningKey = true,
                        IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(options.Secret)),

                        ValidateLifetime = true,//验证过期时间
                        ClockSkew = TimeSpan.FromMinutes(2)//时钟偏移
                    };
                    //捕捉到访问令牌已过期
                    //setupAction.Events = new JwtBearerEvents
                    //{
                    //    OnAuthenticationFailed = context =>
                    //    {
                    //        if (context.Exception.GetType() == typeof(SecurityTokenExpiredException))
                    //        {
                    //            context.Response.Headers.Add("X-Auth-Failed", "expired");//验证失败，token已过期
                    //        }
                    //        return Task.CompletedTask;
                    //    }
                    //};
                });
        }
    }
}
